
#If RETIRED Then

Imports std

'TODO, rewrite netTransData class, use a vector<pair<int32,int32>> to store the start and end position for each item.

Public Class netTransData
    Implements ICloneable

    Public Const stopChar As Byte = 0
    Public Const escapeChar As Byte = 255
    Public Const displayRange As UInt32 = 128

    Protected Friend _field As vector(Of bytes)

    Public Shared Function convertBytes(ByRef value As bytes) As Boolean
        If value Is Nothing Then
            Return False
        Else
            Dim len As Int32 = value.size
            Dim i As Int32
            Dim j As Int32
            Dim rtn As New bytes()
            rtn.size = (len << 1)
            j = 0
            For i = 0 To len - 1
                Select Case value(i)
                    Case stopChar
                        rtn(j) = escapeChar
                        j += 1
                        rtn(j) = stopChar
                        j += 1
                    Case escapeChar
                        rtn(j) = escapeChar
                        j += 1
                        rtn(j) = escapeChar
                        j += 1
                    Case Else
                        rtn(j) = value.data(i)
                        j += 1
                End Select
                'If value.data(i) = stopChar Then
                '    rtn.data(j) = escapeChar
                '    j += 1
                '    rtn.data(j) = stopChar
                '    j += 1
                'ElseIf value.data(i) = escapeChar Then
                '    rtn.data(j) = escapeChar
                '    j += 1
                '    rtn.data(j) = escapeChar
                '    j += 1
                'Else
                '    rtn.data(j) = value.data(i)
                '    j += 1
                'End If
            Next
            rtn.size = j
            value = rtn
            rtn = Nothing

            Return True
        End If
    End Function

    Public Shared Function convertBytesBack(ByRef value() As Byte _
                                            , ByRef start As Int32, ByVal [end] As Int32, ByRef rtn As bytes) As Boolean
        If value Is Nothing Then
            Return False
        Else
            If rtn Is Nothing Then
                rtn = New bytes
            End If
            rtn.size = [end] - start
            Dim i As Int32
            i = 0
            For start = start To [end] - 1
                Select Case value(start)
                    Case escapeChar
                        start += 1
                        rtn(i) = value(start)
                        i += 1
                    Case stopChar
                        start += 1
                        Exit For
                    Case Else
                        rtn(i) = value(start)
                        i += 1
                End Select
                'If value(start) = escapeChar Then
                '    start += 1
                '    rtn(i) = value(start)
                '    i += 1
                'ElseIf value(start) = stopChar Then
                '    start += 1
                '    Exit For
                'Else
                '    rtn(i) = value(start)
                '    i += 1
                'End If
            Next
            rtn.size = i
            Return True
        End If
    End Function

    Public Function available() As Boolean
        Dim i As Int32
        For i = 0 To _field.size() - 1
            If _field.data(i) Is Nothing Then
                Exit For
            End If
        Next

        If i < _field.size() Then
            Return False
        Else
            Return True
        End If
    End Function

    Public Function insert(ByRef values() As bytes, Optional ByVal start As Int32 = 0 _
                            , Optional ByVal size As Int32 = npos) As Boolean
        Return _field.push_back(values, start, size)
    End Function

    Public Function insert(ByRef value As bytes) As Boolean
        Return _field.push_back(value)
    End Function

    Public Function insert(Of valueT)(ByRef value As valueT) As Boolean
        Dim internal As bytes = New bytes(encoding.utf8.GetBytes(Convert.ToString(value)))
        Return insert(internal)
    End Function

    Public Function take(ByVal index As Int32, ByRef buff As bytes) As Boolean
        buff = Nothing
        If index >= _field.size() Or index < 0 Then
            Return False
        Else
            buff = _field(index)
            Return True
        End If
    End Function

    Public Function take(ByVal index As Int32) As bytes
        Dim field As bytes = Nothing
        take(index, field)
        Return field
    End Function

    Public Function take(ByVal index As Int32, ByRef value As Object) As Boolean
        Dim field As bytes = Nothing
        field = take(index)
        If field Is Nothing Then
            Return False
        Else
            Dim str As String
            If Not field.data Is Nothing Then
                str = encoding.utf8.GetString(field.data, 0, field.size)
                value = str
            End If
            Return True
        End If
    End Function

    Public Function take(Of valueT)(ByVal index As Int32) As valueT
        Dim temp As valueT
        If take(index, temp) Then
            Return temp
        Else
            Return Nothing
        End If
    End Function

    Default Public Property data(ByVal index As Int32) As bytes
        Get
            Return _field(index)
        End Get
        Set(ByVal value As bytes)
            _field.set(index, value)
        End Set
    End Property

    Public Function export(ByRef buff() As Byte, ByRef start As Int32, ByRef size As Int32) As Boolean
        Dim i As Int32
        Dim temp As bytes = Nothing
        temp = New bytes
        Dim totalPredictSize As Int32
        For i = 0 To _field.size() - 1
            totalPredictSize += _field(i).size
        Next
        totalPredictSize <<= 1
        totalPredictSize += _field.size()
        If buff Is Nothing Then
            ReDim buff(start - 1 + totalPredictSize)
        Else
            ReDim Preserve buff(start - 1 + totalPredictSize)
        End If
        size = start
        For i = 0 To _field.size() - 1
            temp.copy(_field(i))
            convertBytes(temp)
            Array.Copy(temp.data, 0, buff, size, temp.size)
            size += temp.size
            buff(size) = stopChar
            size += 1
        Next
        ReDim Preserve buff(size)

        Return True
    End Function

    Public Function export(ByRef buff() As Byte, ByRef size As Int32) As Boolean
        Return export(buff, 0, size)
    End Function

    Public Function import(ByRef buff() As Byte, ByVal start As Int32, ByVal size As Int32) As Boolean
        If buff Is Nothing OrElse start + size > buff.Length Then
            Return False
        Else
            Dim temp As bytes = Nothing
            size += start
            While start < size
                If convertBytesBack(buff, start, size, temp) Then
                    insert(temp)
                End If
            End While
            Return True
        End If
    End Function

    Public Function import(ByRef buff() As Byte) As Boolean
        Return import(buff, 0, buff.Length)
    End Function

    Public ReadOnly Property fieldCount() As Int32
        Get
            Return _field.size()
        End Get
    End Property

    Public Sub clone(ByRef value As netTransData)
        _field.clear()
        If Not value Is Nothing Then
            Dim i As Int32
            For i = 0 To value._field.size() - 1
                insert(value._field.data(i))
            Next
        End If
    End Sub

    Public Sub reset()
        _field = New vector(Of bytes)
    End Sub

    Public Sub New()
        reset()
    End Sub

    Public Sub New(ByRef value As netTransData)
        reset()
        clone(value)
    End Sub

    Public Sub clear()
        _field.clear()
    End Sub

    Protected Overrides Sub Finalize()
        clear()
        MyBase.Finalize()
    End Sub

    Public Function display() As String
        Dim rtn As String = Nothing
        Dim i As Int32
        Dim buff As bytes = Nothing
        Dim temp As String = Nothing
        Dim singleRange As Int64
        If _field.size() < 2 Then
            singleRange = displayRange
        Else
            singleRange = displayRange \ _field.size()
        End If
        rtn = "{fieldCount}" + _field.size().ToString
        For i = 0 To min(_field.size() - 1, CType(displayRange, Int32))
            buff = take(i)
            convertString(System.Text.Encoding.UTF8.GetString(buff.data, 0, min(buff.size, singleRange)), temp)
            rtn += character.fullStop
            rtn += character.fullStop
            rtn += character.fullStop
            rtn += character.sheffer
            rtn += character.leftBrace + buff.size.ToString + character.rightBrace + temp
        Next
        Return rtn
    End Function

    Public Function Clone() As Object Implements System.ICloneable.Clone
        Dim rtn As netTransData = Nothing
        rtn = New netTransData(Me)

        Return rtn
    End Function
End Class

#End If
